﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using CalculateModelClasses;

namespace RayTracingModel
{
   public class ReflectEfieldCal
    {
        //私有函数
        #region
        private const int CSpeed = 300;

        //求反射电场强度的垂直分量
       private static Efield VerticalEfield(Efield e, RayInfo rayIn, SpectVector l,double Conduct, double Epara, double s1, double s2, double f)        
        {
            double ReflectAngle = SpectVector.VectorPhase(rayIn.RayVector  ,l );
            Plural VEi = Efield.GetVerticalE(e,rayIn .RayVector ,l );
            Plural V = VerticalReflectance(ReflectAngle,Conduct,f,Epara);
            Plural A = new Plural(s1/(s1+s2 ));
            Plural E = VEi * V * A*GetPhase (s2,f);
            Efield Vefield = SpectVector .VectorDotMultiply (E,SpectVector .VectorCrossMultiply (rayIn .RayVector ,l ));
            return Vefield;
        }

        //求反射电场强度的水平分量
       private static Efield HorizonalEfield(Efield e, RayInfo rayIn, RayInfo rayOut, SpectVector l, double Conduct, double Epara, double s1, double s2, double f)
        {
            double ReflectAngle = SpectVector.VectorPhase(rayIn.RayVector, l);
            Plural  HEi = Efield.GetHorizonalE(e,rayIn .RayVector ,l);
            Plural H = HorizonalReflectance(ReflectAngle, Conduct, f, Epara);
            Plural A = new Plural(s1/(s1+s2 ));
            Plural E = HEi * H * A * GetPhase(s2,f);
            SpectVector l1 = SpectVector.VectorCrossMultiply(rayOut .RayVector ,SpectVector .VectorCrossMultiply (rayIn .RayVector ,l ));
            Efield Hefield =SpectVector .VectorDotMultiply (E,l1 );
            return Hefield;
        }
       
        //获得相位
        private static Plural GetPhase(double s2, double f)
       {
           double WaveLength = CSpeed / f;
           double k = 2 * Math.PI / WaveLength;
           Plural phase = new Plural(Math.Cos(k * s2), Math.Sin(k * s2));
           return phase;
       }
        #endregion

        //求垂直反射系数
       static public Plural VerticalReflectance(double ReflectAngle, double Conduct, double f, double Epara)
       {
           Plural Vreflectance = new Plural();
           double a, b, A, B,C;
           double WaveLength = CSpeed / f;
           Plural temp = new Plural();  //反射系数化简后的复数形式
           temp.Re  = Epara - Math.Sin(ReflectAngle * Math.PI / 180) * Math.Sin(ReflectAngle * Math.PI / 180);
           temp.Im  = 60 * Conduct * WaveLength;
           a = Plural.PluralSqrt (temp).Re ;  //求反射系数的中间量
           b = Plural.PluralSqrt(temp).Im ;  //求反射系数的中间量
           A = Math.Cos(ReflectAngle * Math.PI / 180) * Math.Cos(ReflectAngle * Math.PI / 180) - a * a - b * b;
           B = (a + Math.Cos(ReflectAngle * Math.PI / 180)) * (a + Math.Cos(ReflectAngle * Math.PI / 180)) + b * b;
           Vreflectance.Re = A / B;
           C = -2 * b * Math.Cos(ReflectAngle * Math.PI / 180);
           Vreflectance.Im = C /B ;
           return Vreflectance;
       }

        //求水平反射系数
       static public Plural HorizonalReflectance(double ReflectAngle, double Conduct, double f, double Epara)
       {
           Plural Hreflectance = new Plural();
           double a, b, A, B, C;
           double WaveLength = CSpeed / f;
           Plural temp = new Plural();  //反射系数化简后的复数形式
           temp.Re = Epara - Math.Sin(ReflectAngle * Math.PI / 180) * Math.Sin(ReflectAngle * Math.PI / 180);
           temp.Im = 60 * Conduct * WaveLength;
           double temp1 = 60 * Conduct * WaveLength * Math.Cos(ReflectAngle * Math.PI / 180);
           a = Plural.PluralSqrt(temp ).Re ;
           b = Plural.PluralSqrt(temp ).Im ;
           A = Epara * Epara * Math.Cos(ReflectAngle * Math.PI / 180) * Math.Cos(ReflectAngle * Math.PI / 180) - a * a - b * b + temp1 * temp1;
           B = (Epara * Math.Cos(ReflectAngle * Math.PI / 180) + a) * (Epara * Math.Cos(ReflectAngle * Math.PI / 180) + a) + (b - temp1) * (b - temp1);
           Hreflectance.Re = A / B;
           C = -2 * b * Epara * Math.Cos(ReflectAngle * Math.PI / 180) - 2 * temp1 * a;
           Hreflectance.Im = C / B;
           return Hreflectance;
       }

       //求反射电场总值
       static public Efield ReflectEfield(Efield e, RayInfo rayIn, RayInfo rayOut, SpectVector l, double Conduct, double Epara, double s1, double s2, double f)
       {

           double ReflectAngle = SpectVector.VectorPhase(rayIn.RayVector, l);
           Plural X = new Plural();
           X.Re = VerticalEfield(e, rayIn, l, Conduct, Epara, s1, s2, f).X.Re + HorizonalEfield(e, rayIn, rayOut, l, Conduct, Epara, s1, s2, f).X.Re;
           X.Im = VerticalEfield(e, rayIn, l, Conduct, Epara, s1, s2, f).X.Im + HorizonalEfield(e, rayIn, rayOut, l, Conduct, Epara, s1, s2, f).X.Im;
           Plural Y = new Plural();
           Y.Re = VerticalEfield(e, rayIn, l, Conduct, Epara, s1, s2, f).Y.Re + HorizonalEfield(e, rayIn, rayOut, l, Conduct, Epara, s1, s2, f).Y.Re;
           Y.Im = VerticalEfield(e, rayIn, l, Conduct, Epara, s1, s2, f).Y.Im + HorizonalEfield(e, rayIn, rayOut, l, Conduct, Epara, s1, s2, f).Y.Im;
           Plural Z = new Plural();
           Z.Re = VerticalEfield(e, rayIn, l, Conduct, Epara, s1, s2, f).Z.Re + HorizonalEfield(e, rayIn, rayOut, l, Conduct, Epara, s1, s2, f).Z.Re;
           Z.Im = VerticalEfield(e, rayIn, l, Conduct, Epara, s1, s2, f).Z.Im + HorizonalEfield(e, rayIn, rayOut, l, Conduct, Epara, s1, s2, f).Z.Im;
           Efield E = new Efield(X, Y, Z);
           return E;

       }
    }
}
